import java.text.DecimalFormat;
import java.util.Arrays;
import java.util.List;
import java.util.Map;

public class OutputValueToCSV {
    public void outputValueToCSV(MetricValues metricValues[], List<Packages> packages, List<List<String>> outData, AllMetric allMetric, String isWeight, int allClassNum){

        DecimalFormat decimalFormat = new DecimalFormat("#.#####");
        for(MetricValues metric : metricValues){
            metric.packageIIPE = metric.packageIIPU = 1;
            if(metric.packageUsesSum != 0){
                metric.packageIIPU = 1 - (float)metric.difPackageUsesSum / metric.packageUsesSum;
            }
            if(metric.packageExtSum != 0){
                metric.packageIIPE = 1 - (float)metric.difPackageExtSum / metric.packageExtSum;
            }
            metric.packageIPCI = 1 - (float)metric.packageClientsP.size() / (metricValues.length - 1);
            metric.packagePUF = 1 ;
            if(metric.difPackageUsesPNum != 0) {
                metric.packagePUF = (float) 1 / metric.difPackageUsesPNum;
                metric.packageIIPUD = metric.packagePUF * (1 - (float)(metric.difPackageUsesPNum - 1) / metric.difPackageUsesSum);
            }else {
                metric.packageIIPUD = 1;
            }
            if(metric.difPackageExtPNum != 0) {
                metric.packagePEF = (float) 1 / metric.difPackageExtPNum;
                metric.packageIIPED = metric.packagePEF * (1 - (metric.difPackageExtPNum - 1) / (float)metric.difPackageExtSum);
            }else {
                metric.packageIIPED = 1;
            }
            metric.packagePF = ((float) metric.RoleClientsSum / metric.packageInIntC.size())/ metric.packageClientsP.size();

            // 计算CSCohesion
            for (Map.Entry<Integer, String> entry : metric.providerCSPQ.entrySet()){
                float CSCohesion = 0;
                for (Map.Entry<Integer, String> inEntry : metric.providerCSPQ.entrySet()){
                    if(entry.getKey()!=inEntry.getKey()){
                        CSCohesion += (new CountMatchingCharacters()).countMatchingCharacters(entry.getValue(), inEntry.getValue()) != 0 ? (float) (new CountMatchingCharacters()).countMatchingCharacters(entry.getValue(), inEntry.getValue()) / entry.getValue().length() : 1;
                    }
                }
                metric.csCohesionSum += CSCohesion / metric.packageClientsP.size();
            }
            metric.packageIPSC = metric.csCohesionSum / metric.packageClientsP.size();
            outData.add(Arrays.asList(metric.packageName, decimalFormat.format(metric.packageIIPU), decimalFormat.format(metric.packageIIPE), decimalFormat.format(metric.packageIPCI), decimalFormat.format(metric.packageIIPUD), decimalFormat.format(metric.packageIIPED), decimalFormat.format(metric.packagePF), decimalFormat.format(metric.packageIPSC)));

            if(isWeight.equals("unWeight")){
                // 计算不加权总的结果
                int packageSumNum = packages.size();

                if(!Float.isNaN(metric.packageIPCI)){
                    allMetric.IPCI += ( metric.packageIPCI / packageSumNum );
                }
                if(!Float.isNaN(metric.packageIIPUD)){
                    allMetric.IIPUD += ( metric.packageIIPUD / packageSumNum );
                }
                if(!Float.isNaN(metric.packageIIPED)){
                    allMetric.IIPED += ( metric.packageIIPED / packageSumNum );
                }
                if(!Float.isNaN(metric.packagePF)){
                    allMetric.PF += ( metric.packagePF / packageSumNum );
                }
                if(!Float.isNaN(metric.packageIPSC)){
                    allMetric.IPSC += ( metric.packageIPSC / packageSumNum );
                }
            }else{
                int allClassNumSum = allClassNum;
                if(!Float.isNaN(metric.packageIPCI)){
                    allMetric.IPCI += ( metric.packageIPCI * metric.classNumSum / allClassNumSum );
                }
                if(!Float.isNaN(metric.packageIIPUD)){
                    allMetric.IIPUD += ( metric.packageIIPUD * metric.classNumSum / allClassNumSum );
                }
                if(!Float.isNaN(metric.packageIIPED)){
                    allMetric.IIPED += ( metric.packageIIPED * metric.classNumSum / allClassNumSum );
                }
                if(!Float.isNaN(metric.packagePF)){
                    allMetric.PF += ( metric.packagePF * metric.classNumSum / allClassNumSum );
                }
                if(!Float.isNaN(metric.packageIPSC)){
                    allMetric.IPSC += ( metric.packageIPSC * metric.classNumSum / allClassNumSum );
                }
            }
        }

        allMetric.IIPU = 1;
        if(allMetric.usesSum != 0){
            allMetric.IIPU = 1 - (float) allMetric.difUsesSum / allMetric.usesSum;
        }

        allMetric.IIPE = 1;
        if(allMetric.extSum != 0){
            allMetric.IIPE = 1 - (float) allMetric.difExtSum / allMetric.extSum;
        }

        outData.add(Arrays.asList("AllPackages", decimalFormat.format(allMetric.IIPU), decimalFormat.format(allMetric.IIPE), decimalFormat.format(allMetric.IPCI), decimalFormat.format(allMetric.IIPUD), decimalFormat.format(allMetric.IIPED), decimalFormat.format(allMetric.PF), decimalFormat.format(allMetric.IPSC)));

    }
}
